//==============================================================================
#include "TextBox.h"

using namespace ui;

string const ui::TextBox::TEXTBOX_TYPE = "TEXT_BOX";
//==============================================================================
TextBox::TextBox(int posX, int posY, int width, int height, COMPONENT_TYPE type, string name) : Component(posX, posY, width, height, type, name) {
	SDL_EnableUNICODE(SDL_ENABLE);
	this->active = false;
	this->selected = false;
	this->showText.clear();
	this->fontSize = FONT_SIZE;
	this->posCursor = getXCoordinate() + BEGIN_SPACE;
	this->cursor = false;
}
//------------------------------------------------------------------------------
TextBox::TextBox( int posX, int posY, int width, int height, string defaultText, int fontSize) : Component(posX, posY, width, height,TEXTBOX, defaultText){
	SDL_EnableUNICODE(SDL_ENABLE);
	this->active = false;
	this->selected = false;
	this->showText.clear();
	this->fontSize = fontSize;
	this->posCursor = getXCoordinate()+ BEGIN_SPACE;
	this->cursor = false;
}
//------------------------------------------------------------------------------
TextBox::~TextBox(void){
	SDL_EnableUNICODE( SDL_DISABLE );
}
//------------------------------------------------------------------------------
void TextBox::setText(std::string text){
	this->showText=text;
}
//------------------------------------------------------------------------------
string TextBox::getText(void){
	if(this->showText == getName())
		return "";
	else
		return this->showText;
}
//------------------------------------------------------------------------------
void TextBox::setSelected(bool select){
	this->selected = select;
}
//------------------------------------------------------------------------------
void TextBox::clearBox(){
	this->showText.clear();
}
//------------------------------------------------------------------------------
void TextBox::drawBox(SDL_Surface* s) throw (SDL_Exception)
{
	SDL_Rect textArea;
	textArea.x = getXCoordinate();
	textArea.y = getYCoordinate();
	textArea.w = getWidth();
	textArea.h = getHeight();
	if (this->selected)
	{
		if(SDL_FillRect( s, &textArea, ORANGE))
            throw SDL_Exception( std::string("TEXTBOX - SDL_FillRect - ERROR"));
	}
	else
	{
		if(SDL_FillRect( s, &textArea, WHITE))
            throw SDL_Exception( std::string("TEXTBOX - SDL_FillRect - ERROR"));
	}
}
//------------------------------------------------------------------------------
void TextBox::draw(SDL_Surface* s) throw (SDL_Exception)
{
    try
    {
		if(this->active)
				this->cursor = !this->cursor;
        this->drawBox(s);
        this->drawText(s);
		if(this->active && this->cursor)
			this->drawCursor(s);
	}
	catch(SDL_Exception &ex)
	{
		throw ex;
	}
}
//------------------------------------------------------------------------------
void TextBox::drawText(SDL_Surface* s) throw (SDL_Exception)
{
	SDL_Rect boxArea;
	boxArea.x = getXCoordinate();
	boxArea.y = getYCoordinate();
	boxArea.w = getWidth();
	boxArea.h = getHeight();

	TTF_Font* font = TTF_OpenFont("Arial.ttf", fontSize);
    if(!font)
    {
        std::string errorMessage("TEXTBOX - TTF_OpenFont - ERROR");
        throw(SDL_Exception(errorMessage));
    }
	SDL_Color textColor = {0, 0, 0};
	SDL_Rect textArea = boxArea;
	textArea.y += 5;
	textArea.x += BEGIN_SPACE;
	if(this->showText.empty() && !this->active)
		this->showText = getName();
	else
		if(this->active && this->showText == getName())
			 this->showText.clear();
	SDL_Surface* message = TTF_RenderText_Solid(font, this->showText.c_str(), textColor);
	TTF_CloseFont(font);
		
	if (message != NULL)
	{		
		//Check width of the renderized text to show compared with box width.
		boxArea = message->clip_rect;
		int dif = boxArea.w - getWidth();
		if (dif >= -END_SPACE)
		{
			boxArea.x += dif + END_SPACE;
			boxArea.w = textArea.w;
		}
		if(SDL_BlitSurface(message, &boxArea, s, &textArea))
		{
			SDL_FreeSurface(message);
			std::string errorMessage("TEXTBOX - BLIT SURFACE MESSAGE - ERROR");
			throw SDL_Exception (errorMessage);
		}
		if(this->active)
		{
			this->posCursor = textArea.x + textArea.w;
		}
	}
	else
	{
		if(this->active)
		{
			this->posCursor = textArea.x;
		}
		SDL_BlitSurface(message, &boxArea, s, &textArea);
	}
			
	SDL_FreeSurface(message);
}
//------------------------------------------------------------------------------
void TextBox::drawCursor(SDL_Surface* s)
{
	Draw_Line(s,this->posCursor, getYCoordinate()+1,this->posCursor, getYCoordinate() + getHeight() - 3, BLACK);
}

//------------------------------------------------------------------------------
bool TextBox::isClicked(SDL_Event* event)
{
	if(event->type == SDL_MOUSEBUTTONDOWN && event->button.button == SDL_BUTTON_LEFT && ocurredInside(event->button.x, event->button.y))
		return true;
	else
		return false;
}
//------------------------------------------------------------------------------
COMPONENT_TYPE TextBox::handleEvent(SDL_Event* event)
{
	COMPONENT_TYPE type = NONE;

	//Si se presiono el boton izquierdo del mouse
	if(event->type == SDL_MOUSEBUTTONDOWN && event->button.button == SDL_BUTTON_LEFT)
	{
		if(ocurredInside(event->button.x,event->button.y))
			this->active = true;
		else
			this->active = false;
    }
	
    //Si se presiono una tecla del teclado y se encontraba activa la textbox
	if(event->type == SDL_KEYDOWN && this->active)
	{
		//Si la tecla fue el Espacio
		if(event->key.keysym.sym >= SDLK_SPACE && event->key.keysym.sym <= SDLK_z)
		{
			//Append the character
			this->showText += (char)event->key.keysym.unicode;
		}
		else
			if( (event->key.keysym.sym == SDLK_BACKSPACE) && (!this->showText.empty()) )
			{
				//Remove a character from the end
				this->showText.erase(this->showText.length() - 1);
			}
			else
				if( (event->key.keysym.sym == SDLK_ESCAPE) || (event->key.keysym.sym == SDLK_DELETE) && (!this->showText.empty()) )
				{
					//Remove a character from the end
					this->showText.clear();
				}
	}
	return type;
}
//==============================================================================
